// /**
//  * 代码中的类名、方法名、参数名已经指定，请勿修改，直接返回方法规定的值即可
//  *
//  * 
//  * @param s string字符串 
//  * @return int整型
//  */
//  function lengthOfLongestSubstring( s ) {
//   // write code here
//   let sIndex = {}
//   let res = 0
//   let i = -1 // 左边界
//   let j = 0
//   while(j < s.length){
//     if(sIndex.hasOwnProperty(s[j])){
//       i = sIndex[s[j]] > i ? sIndex[s[j]] : i // 这种情况是为了避免 重复出现的字符在此时最长字符串的前面 如果出现在前面的话呢么最长字符串就还是原来的 如果不在前面的话 左边界就应该更新
//     }
//     sIndex[s[j]] = j // 修改映射中对于的值
//     res = res > j - i ? res : j - i // 不断更新着最大值
//     j++
//   }
//   return res
// }
// module.exports = {
//   lengthOfLongestSubstring : lengthOfLongestSubstring
// };

/**
 * 代码中的类名、方法名、参数名已经指定，请勿修改，直接返回方法规定的值即可
 *
 * 
 * @param s string字符串 
 * @return int整型
 */
 function lengthOfLongestSubstring( s ) {
  // write code here
  let res = 0
  let i = -1
  let hasIndex = {}
  let j = 0
  while(j < s.length){
    if(hasIndex.hasOwnProperty(s[j])){
      i = i > hasIndex[s[j]] ? i : hasIndex[s[j]]
    }
    hasIndex[s[j]] = j
    res = res > j - i ? res : j -i
    j++
  }
  return res
}
module.exports = {
  lengthOfLongestSubstring : lengthOfLongestSubstring
};